////////////////////////////////////////////////////////////////////////////////
//                                                                            //
//  Filename:    FameAndFortuneGuts.cpp                                       //
//  Developer:   Gilbert Araya                                                //
//  Create date: 09/10/2007                                                   //
//                                                                            //
////////////////////////////////////////////////////////////////////////////////
//                                                                            //
//  Description: This is the class implementation for the slot gut of the     //
//               Australian Slot machine called Fame&Fortune.               //
//                                                                            //
////////////////////////////////////////////////////////////////////////////////
//        Copyright (c) 2007 - Realtime Gaming.  All rights reserved.         //
////////////////////////////////////////////////////////////////////////////////

#include "FameAndFortuneGuts.h"

////////////////////////////////////////////////////////////////////////////
/// FameAndFortuneGuts::m_aLineWinSpinResults
///
/// This array is used to quickly get the SpinResult for the number of
/// icons.  It is indexed by wheel icon and then count.  So to get the
/// SpinResult for 5 Aces, use the following code snippet:
///
///		SpinResult result = m_aLineWinSpinResults[ ICON_ACE ][ 5 ];
///
/// In this example result would be set to EVT_FIVE_ACE.
////////////////////////////////////////////////////////////////////////////
 FameAndFortuneGuts::SpinResult FameAndFortuneGuts::m_aLineWinSpinResults[][6] = 
 {
 // Number of icons:			0			1					2					3						4				    5
 /* ICON_NINE */			{	EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_THREE_NINE,			EVT_FOUR_NINE,		EVT_FIVE_NINE      },
 /* ICON_TEN */				{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_THREE_TEN,			EVT_FOUR_TEN,		EVT_FIVE_TEN       },
 /* ICON_JACK */			{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_THREE_JACK,			EVT_FOUR_JACK,		EVT_FIVE_JACK      },
 /* ICON_QUEEN */			{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_THREE_QUEEN,		EVT_FOUR_QUEEN,		EVT_FIVE_QUEEN     },
 /* ICON_KING */			{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_THREE_KING,			EVT_FOUR_KING,		EVT_FIVE_KING      },
 /* ICON_ACE */				{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_THREE_ACE,			EVT_FOUR_ACE,		EVT_FIVE_ACE       },
 /* ICON_CAR */				{   EVT_LOSER,	EVT_LOSER,			EVT_TWO_CAR,		EVT_THREE_CAR,			EVT_FOUR_CAR,		EVT_FIVE_CAR       },
 /* ICON_HOLLYWOOD */		{   EVT_LOSER,	EVT_ONE_HOLLYWOOD,	EVT_TWO_HOLLYWOOD,	EVT_THREE_HOLLYWOOD,	EVT_FOUR_HOLLYWOOD,	EVT_FIVE_HOLLYWOOD },
 /* ICON_TROPHY */			{   EVT_LOSER,	EVT_LOSER,			EVT_TWO_TROPHY,		EVT_THREE_TROPHY,		EVT_FOUR_TROPHY,	EVT_FIVE_TROPHY	   },
 /* ICON_GLAMOUR_GIRL */	{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_LOSER,				EVT_LOSER,			EVT_LOSER	       },
 /* ICON_FAME */			{   EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_LOSER,				EVT_LOSER,			EVT_LOSER	       },
 /* ICON_FORTUNE */			{	EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_LOSER,				EVT_LOSER,			EVT_LOSER	       },
 /* ICON_DIAMOND */			{	EVT_LOSER,	EVT_LOSER,			EVT_LOSER,			EVT_LOSER,				EVT_LOSER,			EVT_LOSER	       }
 };

////////////////////////////////////////////////////////////////////////////
/// FameAndFortuneGuts::m_aScatterWinSpinResults
///
/// This array is used to quickly get the SpinResult for the number of
/// icons.  It is indexed by icon count only, since Fame and Fortune are the only
/// scatter win during the normal game.  So to get the SpinResult for Fame and Fortune, 
/// which in this case should be 2, use the following code snippet:
///
///		SpinResult result = m_aScatterWinSpinResults[ 2 ];
///
/// In this example result would be set to EVT_TWO_FORTUNE.
////////////////////////////////////////////////////////////////////////////
FameAndFortuneGuts::SpinResult FameAndFortuneGuts::m_aScatterWinSpinResults[6] = 
{
	//ICON_FLAG	Number of Icons
	EVT_LOSER,	     // 0
	EVT_LOSER,	     // 1
	EVT_TWO_FORTUNE, // 2 - Represents the payout when the icons ICON_FAME and ICON_FORTUNE shows up
	EVT_LOSER,	     // 3
	EVT_LOSER,	     // 4
	EVT_LOSER 	     // 5
};

////////////////////////////////////////////////////////////////////////////
/// FameAndFortuneGuts::m_aScatterFreeSpinResults
///
/// This array is used to quickly get the SpinResult for the number of
/// icons.  It is indexed by icon count only, since Diamonds are the only
/// scatter win during Free games.  So to get the SpinResult for 5 Diamonds, use the
/// following code snippet:
///
///		SpinResult result = m_aScatterWinSpinResults[ 5 ];
///
/// In this example result would be set to EVT_FIVE_DIAMOND.
////////////////////////////////////////////////////////////////////////////
FameAndFortuneGuts::SpinResult FameAndFortuneGuts::m_aScatterFreeSpinResults[6] = 
{
	//ICON_FLAG        Number of Icons
	EVT_LOSER,		   // 0
	EVT_LOSER,		   // 1
	EVT_TWO_DIAMOND,   // 2
	EVT_THREE_DIAMOND, // 3
	EVT_FOUR_DIAMOND,  // 4
	EVT_FIVE_DIAMOND   // 5

};
////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::FameAndFortuneGuts()   
///
/// This is the default constructor for the class.
////////////////////////////////////////////////////////////////////////////
FameAndFortuneGuts::FameAndFortuneGuts()
{
	// If this doesn't compile it means that someone probably added
	// another icon type but did not update the
	// m_aLineWinSpinResults array. 
	C_ASSERT( countof( m_aLineWinSpinResults ) == NUM_VALID_ICONS );
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::~FameAndFortuneGuts()
///
/// Destructor for FameAndFortuneGuts. 
////////////////////////////////////////////////////////////////////////////
FameAndFortuneGuts::~FameAndFortuneGuts()
{
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::SpinResult FameAndFortuneGuts::getLineWinResultWithPossibleSubstitution( uint8* stops, uint8 testIcon, bool& bSubstitution ) const
///
/// @param   stops			The array of stop positions for the line.
/// @param   testIcon		The icon we are looking for, typically the first icon on the line.
/// @param   bSubstitution	An output parameter that is set if a subsitution is used.
///
/// @return	 SpinResult		A payout from the SpinResult enumeration.
///
/// This helper method is used to calculate the line win payout with a possible substitution.
////////////////////////////////////////////////////////////////////////////
FameAndFortuneGuts::SpinResult FameAndFortuneGuts::getLineWinResultWithPossibleSubstitution(
	uint8* stops, uint8 testIcon, bool& bSubstitution ) const
{
	// Initialize the out parameter
	bSubstitution = false;

	// Loop through the remaining reels until the streak is over
	for ( int i = 1; i < getReelCount(); i++ )
    {
		// See what this icon is.
		uint8 currentIcon = getIcon( getGameModeId(), i, stops[i] )->iconid;

		// If the current icon is a Glamour Girl (Substitute) ...
		// The ICON_FORTUNE is tested but, it should not ocurr because the testIcon is always the first one and the ICON_FORTUNE only
		// shows up in the last reel.
		if ( (currentIcon == ICON_GLAMOUR_GIRL) && (testIcon != ICON_DIAMOND) && (testIcon != ICON_FAME) && (testIcon != ICON_FORTUNE) ) 
		{
			// then use it as a substitution symbol and continue on.
			bSubstitution = true;
			continue;
		}
		// Otherwise if the test icon is a Glamour Girl...
		else if ( testIcon == ICON_GLAMOUR_GIRL )
		{
			// then we still have a substitution.  In this case the line
			// started out with a Substitution symbol, which should never happen in this game.
			ASSERT( false );
			break;
		}

		// If the current icon is not the test icon...
        if ( currentIcon != testIcon )
        {
			// then the streak is over so break out of the loop
			break;
        }
    }

	// This should never happen in this game because there aren't 
	// any Glamour Girls on the first or last reel.
	ASSERT( testIcon != ICON_GLAMOUR_GIRL )

	// Use the array to look up the spin result for i testIcons.
	return lookupLineWinSpinResult( testIcon, i );
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::classifyStops()   
///
/// @param   stops      The array of stop positions for the line.
/// @param   bet        The value of the line bet.
/// @param   line       The index of the line.
///
/// @return	 uint8      A payout from the SpinResult enumeration as a uint8.    
///
/// This helper method is used to calculate the payout on a line.
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::classifyStops( SpinLine* spinline, uint8* stops, uint8 bet, uint8 line,
	uint8& rtnresult, uint8& multiplier )
{

	// See what the payout is if we use any Pilots we find as substitution symbols.
	// Start with the icon on the first reel.
	uint8 testIcon = getIcon( getGameModeId(), 0, stops[0] )->iconid;

	// Declare a local variable to track whether or not we found a substitution.
	bool bSubstitution = false;

	// See what is the spin result is if we used any Glamour Girls as substitution symbols.
	rtnresult =	getLineWinResultWithPossibleSubstitution( stops, testIcon, bSubstitution );

	// If we did actually have a substitution and a winning spin...
	if ( bSubstitution && rtnresult != EVT_LOSER )
	{
		// then if the winning spins is NOT one Hollywood
		if ( rtnresult != EVT_ONE_HOLLYWOOD ) 
		{
			multiplier = MULTIPLIER_SUBSTITUTION;
			spinline->addNote( NOTE_SUBSTITUTION );
		}
	}
}

////////////////////////////////////////////////////////////////////////////
/// @fn		FameAndFortuneGuts::tryForJackpot()
///
///	This function looks to see if we hit the jackpot.
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::tryForJackpot( SlotSpin* spin )
{
	// If we are in the first paid spin (NOT a bonus spin)...
	if ( getGameModeId() == MODE_NORMAL ) 
	{
		// then try for the Random Progressive Jackpot
		// If we hit the jackpot...
		if ( getRandomProgressiveJackpotResult( getNumLinesBet() ) || 
             m_bForceRandomJackpot == true )
		{
			// then add a jackpot scatter to the spin.
			spin->addScatter( 0,
				getPayout( EVT_RANDOM_PROGRESSIVE_WINNER )->payoutAmount, 1,
				true, EVT_RANDOM_PROGRESSIVE_WINNER, 0 );
		}
    }
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::getScatterWinResult()   
///
/// @param   spin						The current spin object.
/// @param   nNumScatterIcons			The number of scatter icons that we find.
/// @param   nScatterPositions			The bit mask for the scatters positions that we find.
///
/// @return	 SpinResult			A payout from the SpinResult enumeration.
///
/// This helper method is used to evaluate the spin for scatters.
////////////////////////////////////////////////////////////////////////////
FameAndFortuneGuts::SpinResult FameAndFortuneGuts::getScatterWinResult( SlotSpin* spin, 
																	    int32&    nNumScatterIcons, 
																		int32&    nScatterPositions ) const
{
	// Initialize the scatterPositions.
	nScatterPositions = 0;

	// Loop through each reel.
  	for( int reel = 0; reel < getReelCount(); reel++ )
	{
		// The position bit for the current icon in case it needs to be stored in a mask.
		uint8 position = reel;

		// Loop through each row in the wheel house.
		for( int row = 0; row < 3; row++ )
		{
			// Get the current stop.
			uint8 stop = relativeWheelPosition( getGameModeId(), reel,
				spin->getStops()[ reel ], row );

			// Get the icon for the current stop.
			uint8 currentIcon = getIcon( getGameModeId(), reel, stop )->iconid;
			
			// If the icon is the one we are looking for...

			// In the Normal Game mode the only Scatter icons that can occur are the ICON_FAME or ICON_FORTUNE
			// In the Free   Game mode the only Scatter icon  that can occur is  the ICON_DIAMOND
			if ( currentIcon == ICON_FAME || currentIcon == ICON_FORTUNE || currentIcon == ICON_DIAMOND)
			{
				// then increase the icon count
				nNumScatterIcons++;

				// Set the bit in the position mask for this stop.
				nScatterPositions |= 1 << position;
			}

			// Move to the next bit in the position mask.
            position += 5;
		}
	}

	// Use the array to look up the spin result for nNumScatterIcons.
	return lookupScatterWinSpinResult( nNumScatterIcons, getGameModeId() );
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::addScatterWin()
///
/// This function determines if the current spin wins a scatter payment and
/// adds the scatter.
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::addScatterWin( SlotSpin* spin, SpinResult srScatterResult, int32 nScatterPositions )
{
	int iCurrentFreeSpin = 0;

	if (getGameModeId() == MODE_FREE_SPIN)
	{
		iCurrentFreeSpin = getCurrentFreeSpin() + 1;

		if ( iCurrentFreeSpin <= 5 ) 
		{
			decrease2XFreeSpins();
		}
		//This is for the Free Spins 6-10, when the wins are tripled
		else
		{
			decrease3XFreeSpins();
		}
	}

	// If we got the scatter win...
	if ( srScatterResult != EVT_LOSER )
	{
		// then initialize our multiplier for scatters.
		int32 multiplier = 1;

		
		int nFreeSpinNoteId  = 0;

		//If we are in Free Games and a winning spin...
		if (getGameModeId() == MODE_FREE_SPIN)
		{
			iCurrentFreeSpin = getCurrentFreeSpin() + 1;

			ASSERT((iCurrentFreeSpin >= 0) && (iCurrentFreeSpin <= 10))

			//This is for the Free Spins 1-5, when the wins are doubled
			if ( iCurrentFreeSpin <= 5 ) 
			{
				// then add a note.
				nFreeSpinNoteId = NOTE_FREE_SPIN_DOUBLE;
				// then define the multiplier
				multiplier = MULTIPLIER_FREE_SPIN_DOUBLE;
			}
			//This is for the Free Spins 6-10, when the wins are tripled
			else
			{
				// then add a note.
				nFreeSpinNoteId = NOTE_FREE_SPIN_TRIPLE;
				// then define the multiplier
				multiplier = MULTIPLIER_FREE_SPIN_TRIPLE;
			}
		}

		// Get the base payout for the scatter.
		int32 nPayout = getPayout( srScatterResult )->payoutAmount;
		
		// Scatters payout based on the total bet, so factor in the number of bet lines.
		nPayout *= spin->getSpinLineCount();

		// Add the payout (with multiplier) to the total win for this spin.
		increaseTotalWin( nPayout * multiplier );
    
		// Add a scatter to the spin.
		SlotScatter* pScatter = spin->addScatter( nScatterPositions,
			nPayout * getBetPerLine(), multiplier, false, srScatterResult, 0 );
		
		if (getGameModeId() == MODE_FREE_SPIN)
		{
			pScatter->addNote( nFreeSpinNoteId );
		}
	}
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::addFeatureTrigger()
///
/// This function determines if the current spin triggered the free game
/// feature and adds the appropriate scatter.
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::addFeatureTrigger( SlotSpin* spin, int32& nNumScatterIcons, int32 nFeatureScatterPositions )
{
	// We need a place to keep up with how many free spins to award.
	int32 nFreeSpins = 0;

	// Also keep up with what type of feature trigger it is.
	SpinResult srFeatureResult = EVT_LOSER;

	// Figure out how many free spins they get.

	if ( getGameModeId() == MODE_NORMAL )
	{
		if (nNumScatterIcons == 1)
		{
			srFeatureResult = EVT_FEATURE_NEAR_MISS;
		}
		else if (nNumScatterIcons == 2)
		{
			nFreeSpins = 10;
			srFeatureResult = EVT_FREE_GAME_FEATURE;
			
			setCurrentFreeSpin(0); //Initializes the Free Spin Counter

			set2XFreeSpins(0); //Initilizes the 2x multiplier free spins
			set3XFreeSpins(0); //Initilizes the 3x multiplier free spins
		}
		else
		{
			ASSERT( nNumScatterIcons <= 2 ); //In the normal mode there should not be more than 2 Scatter Icons (Fame and Fortune)
		}
	}
	else
	{   //In the Free Spin mode there could be: 1 to 5 Diamonds.
		
		if ( nNumScatterIcons == 2 )
		{
			srFeatureResult = EVT_FEATURE_NEAR_MISS;
		}
		else if ( nNumScatterIcons >= 3 )
		{
			nFreeSpins = 10;
			srFeatureResult = EVT_FREE_GAME_FEATURE;
		}
		
		int iCurrentFreeSpin = getCurrentFreeSpin() + 1;
		//Calculate the next Free Game number
		iCurrentFreeSpin = (iCurrentFreeSpin % 10); //The free games are always on sets of 10 games
		
		//Store the Free Game Number in the SubGame array
		setCurrentFreeSpin(iCurrentFreeSpin);  

	}

	// If they get free spins...
	if ( nFreeSpins )
	{
		// then change the game mode.
		setGameModeId( MODE_FREE_SPIN );

		// Add the free spins.
		incrementFreeSpins( nFreeSpins );

		increment2XFreeSpins(nFreeSpins/2);
		increment3XFreeSpins(nFreeSpins/2);
	}

	// If we had a trigger or a near miss...
	if ( srFeatureResult != EVT_LOSER )
	{
		// then add a scatter to the spin for the feature trigger.
		spin->addScatter( nFeatureScatterPositions, 0, 0, false,
			srFeatureResult, nFreeSpins );
	}
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::classifyScatters( SlotSpin* spin )
///
/// @param   spin       Pointer to the spin with stop data.
///
/// This is an override of the framework method.  
/// It determines if the current spin merits free spins or scatter payments.
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::classifyScatters( SlotSpin* spin )
{	
	// Try for the Random Progressive Jackpot
	tryForJackpot( spin );

	// Declare some local variables to track the scatter positions.
	int32 nScatterPositions = 0;
	int32 nNumScatterIcons = 0;

	// See if there is a scatter win.
	SpinResult srResult = getScatterWinResult( spin, nNumScatterIcons, nScatterPositions );

	// Add the scatter, if any.
	addScatterWin( spin, srResult, nScatterPositions );

	// Add the scatters for the free game feature or near miss.
	addFeatureTrigger( spin, nNumScatterIcons, nScatterPositions );
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::isValidGuts()   
///
/// @return	 bool8      True if gut is valid.    
///
/// This helper method is used to see if the current gut ID is valid.
////////////////////////////////////////////////////////////////////////////
bool8 FameAndFortuneGuts::isValidGuts()
{
	// Make sure that the m_aLineWinSpinResults array has an entry for each reel,
	// and an additional entry in case there are 0 icons on the line.
	// Note:  we can't do this in the constructor because we have to call
	// getReelCount.
	ASSERT( countof( m_aLineWinSpinResults[0] ) == getReelCount( MODE_NORMAL ) + 1 );

	// Make sure that the m_aScatterWinSpinResults array has an entry for each reel,
	// and an additional entry in case there are 0 icons on the line.
	ASSERT( countof( m_aScatterWinSpinResults ) == getReelCount( MODE_NORMAL ) + 1 );
	ASSERT( countof( m_aScatterFreeSpinResults ) == getReelCount( MODE_NORMAL ) + 1 );

	// Now make sure that all game modes have the same number of reels.
	ASSERT( getReelCount( MODE_NORMAL ) == getReelCount( MODE_FREE_SPIN ) );

	// Finally just check to see if the gut is within the right range.
    return ( getGutsId() >= 3900 && getGutsId() < 4000 );
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::getGameModeMultiplierAndNoteId( uint8& nGameModeMultiplier, uint8& nNoteId )
///
/// @param   nGameModeMultiplier	The multiplier for the game mode.
/// @param   nNoteId				The note ID for the game mode.
///
/// This helper method is used to get the game mode multiplier and note ID.
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::getGameModeMultiplierAndNoteId( uint8& nGameModeMultiplier,
	uint8& nNoteId )
{
	if (getGameModeId() == MODE_FREE_SPIN)
	{
		int iCurrentFreeSpin = getCurrentFreeSpin() + 1;

		ASSERT((iCurrentFreeSpin >= 1) && (iCurrentFreeSpin <= 10))

		if ( iCurrentFreeSpin <= 5 ) 
		//This is for the Free Spins 1-5, when the wins are doubled
		{
			// then add a note.
			nNoteId = NOTE_FREE_SPIN_DOUBLE;
			// then define the multiplier
			nGameModeMultiplier = MULTIPLIER_FREE_SPIN_DOUBLE;
		}
		//This is for the Free Spins 6-10, when the wins are tripled
		else
		{
			// then add a note.
			nNoteId = NOTE_FREE_SPIN_TRIPLE;
			// then define the multiplier
			nGameModeMultiplier = MULTIPLIER_FREE_SPIN_TRIPLE;
			//decrease3XFreeSpins();
		}
		
		//Calculate the next Free Game number
		//iCurrentFreeSpin = (iCurrentFreeSpin % 10); //The free games are always on sets of 10 games
		
		//Store the Free Game Number in the SubGame array
		//setCurrentFreeSpin(iCurrentFreeSpin);  
	}	
	// Otherwise...
    else
    {
		// just defer to the base class.
        SlotGuts::getGameModeMultiplierAndNoteId( nGameModeMultiplier, nNoteId );    
	}
}

////////////////////////////////////////////////////////////////////////////
/// @fn 	 FameAndFortuneGuts::Debug_SetLoserStops( uint8* pStops )
///
/// @param   pStops		The stops to set.
///
/// Base class override, returns a losing spin triggered by the debug tool
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::Debug_SetLoserStops( uint8* pStops )
{
	pStops[0]=2;
	pStops[1]=0;
	pStops[2]=0;
	pStops[3]=0;
	pStops[4]=0;
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : getCurrentFreeSpin()
///
/// DESCRIPTION  : Gets the current Free Spin number.
///
/// PARAMETERS   : None.
///
/// RETURN VALUE : Current spin number. This value is in the range from 0 to 9. 
///
/// HISTORY      : 2007/09/18 - Creation.
////////////////////////////////////////////////////////////////////////////
uint8 FameAndFortuneGuts::getCurrentFreeSpin() //Used to get the current spin number during a free spin game
{
	// Just return the subgame data.
	return m_subGame->getData( SGDIDX_CURRENT_FREE_SPIN );
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : setCurrentFreeSpin()
///
/// DESCRIPTION  : Sets the current Free Spin number.
///
/// PARAMETERS   : nFreeSpin = Number between 0 to 9 indicating the current Free Spin.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/09/18 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::setCurrentFreeSpin( uint8 nFreeSpin ) //Sets the current Free Spin number
{
	// Just store the new value in the subgame data.
    m_subGame->update( SGDIDX_CURRENT_FREE_SPIN, nFreeSpin );
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : get2XFreeSpinsRemaining()
///
/// DESCRIPTION  : Gets the current 2X Free Spins remaining.
///
/// PARAMETERS   : None.
///
/// RETURN VALUE : Current spin number. 
///
/// HISTORY      : 2007/12/12 - Creation.
////////////////////////////////////////////////////////////////////////////
int32 FameAndFortuneGuts::get2XFreeSpinsRemaining() //Used to get the current spin number during a free spin game
{
	// Just return the subgame data.
	return m_subGame->getData( SGDIDX_2X_FREE_SPINS_REMAINING );
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : set2XFreeSpins()
///
/// DESCRIPTION  : Sets the current 2X Free Spins remaining.
///
/// PARAMETERS   : n2XFreeSpins = Amount of 2XFreeSpins.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/12/12 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::set2XFreeSpins( int32 n2XFreeSpins ) //Sets the current Free Spin number
{
	// Just store the new value in the subgame data.
    m_subGame->update( SGDIDX_2X_FREE_SPINS_REMAINING, n2XFreeSpins );
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : increment2XFreeSpins()
///
/// DESCRIPTION  : Increment the amout of 2X Free spins remaining in the specified amount.
///
/// PARAMETERS   : n2XFreeSpins = Amount of 2XFreeSpins.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/12/12 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::increment2XFreeSpins(int32 n2XFreeSpins)
{
	int32 i2XFreeSpins = get2XFreeSpinsRemaining();
	i2XFreeSpins = i2XFreeSpins + n2XFreeSpins;
	set2XFreeSpins(i2XFreeSpins);
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : decrease2XFreeSpins()
///
/// DESCRIPTION  : Decreases the amout of 2X Free spins remaining by 1.
///
/// PARAMETERS   : None.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/12/12 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::decrease2XFreeSpins()
{
	int32 i2XFreeSpins = get2XFreeSpinsRemaining();
	i2XFreeSpins = i2XFreeSpins - 1;
	set2XFreeSpins(i2XFreeSpins);
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : get3XFreeSpinsRemaining()
///
/// DESCRIPTION  : Gets the current 3X Free Spins remaining.
///
/// PARAMETERS   : None.
///
/// RETURN VALUE : Current spin number. 
///
/// HISTORY      : 2007/12/12 - Creation.
////////////////////////////////////////////////////////////////////////////
int32 FameAndFortuneGuts::get3XFreeSpinsRemaining() //Used to get the current spin number during a free spin game
{
	// Just return the subgame data.
	return m_subGame->getData( SGDIDX_3X_FREE_SPINS_REMAINING );
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : set3XFreeSpins()
///
/// DESCRIPTION  : Sets the current 3X Free Spins remaining.
///
/// PARAMETERS   : n3XFreeSpins = Amount of 3XFreeSpins.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/12/12 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::set3XFreeSpins( int32 n3XFreeSpins ) //Sets the current Free Spin number
{
	// Just store the new value in the subgame data.
    m_subGame->update( SGDIDX_3X_FREE_SPINS_REMAINING, n3XFreeSpins );
}


////////////////////////////////////////////////////////////////////////////
/// NAME         : increment3XFreeSpins()
///
/// DESCRIPTION  : Increment the amout of 3X Free spins remaining in the specified amount.
///
/// PARAMETERS   : n3XFreeSpins = Amount of 3XFreeSpins.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/12/12 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::increment3XFreeSpins(int32 n3XFreeSpins)
{
	int32 i3XFreeSpins = get3XFreeSpinsRemaining();
	i3XFreeSpins = i3XFreeSpins + n3XFreeSpins;
	set3XFreeSpins(i3XFreeSpins);
}

////////////////////////////////////////////////////////////////////////////
/// NAME         : decrease3XFreeSpins()
///
/// DESCRIPTION  : Decreases the amout of 3X Free spins remaining by 1.
///
/// PARAMETERS   : None.
///
/// RETURN VALUE : None.
///
/// HISTORY      : 2007/12/12 - Creation
////////////////////////////////////////////////////////////////////////////
void FameAndFortuneGuts::decrease3XFreeSpins()
{
	int32 i3XFreeSpins = get3XFreeSpinsRemaining();
	i3XFreeSpins = i3XFreeSpins - 1;
	set3XFreeSpins(i3XFreeSpins);
}